package HomeWork1WalkMazePro;

import java.util.ArrayList;
import java.util.Random;
import java.util.Scanner;

public class WalkMazePro {
    final static int row = 8;
    final static int col = 8;
    final static int door = 0;//地板 ▢
    final static int wall = 1;//墙 ▣
    final static int monster = 2;//怪
    final static int potion = 3;//药水  ◈
    final static int armor = 4;//盔甲
    final static int weapon = 5;//武器
    public static void main(String[] args) {

        //创建角色
        Role role = new Role('p');
        ArrayList<Equipment> bag = new ArrayList<>();
        role.setBag(bag);//添加背包
        //创建装备
        ArrayList<Equipment> equipments = createEquipment();
        //打印菜单
        printMenu();
        //玩游戏
        playGame(role,equipments);
    }



    //游戏主体
    private static void playGame( Role role,ArrayList<Equipment> equipments) {
        Scanner sc = new Scanner(System.in);
        //初始化迷宫
        int[][] maze = generateMaze(row,col);
        int x = 0;
        int y = 0;
        //打印迷宫
        printMaze(maze,x,y,role);
        while(true) {
            String input = sc.nextLine();
            switch(input) {
                case "w":
                    x = up(x, y, role, maze);//向上走
                    break;
                case "s":
                    x = down(x, y, role, maze);//向下走
                    break;
                case "a":
                    y = left(x, y, role, maze);//像左走
                    break;
                case "d":
                    y = right(x, y, role, maze);//像右走
                    break;
                case "e":
                    lookBag(role);//查看背包
                    break;
                case "r":
                    usePotion(role.getBag(),role);
                    break;
                case "t":
                    lookRoleState(role);
                    break;
                default:
                    System.out.println("请重新输入");
            }

            walk(x,y,role,maze,equipments);

            if (x == row - 1 && y == col - 1) {
                System.out.println("恭喜你成功走出迷宫,想要再玩一把吗？  yes /  no ");
                String answer = sc.nextLine();
                if (answer.equals("yes")) {
                    maze = generateMaze(row, col);
                    x = 0;
                    y = 0;
                    printMaze(maze, x, y, role);
                } else {
                    System.out.println("感谢游玩");
                    break;
                }
            }else if(role.getBlood() <=0){
                System.out.println("你未能成功走出迷宫，游戏结束，请重新开始游戏");
                break;
            }

        }
    }


    //捡到武器
    private static void offense(int x, int y, Role role, int[][] maze,ArrayList<Equipment> Weapons ,Scanner sc) {
        Random rand = new Random();
        int index = rand.nextInt(3) + 3;
        Weapon weapon = (Weapon) Weapons.get(index);
        System.out.println("你捡到了"+weapon.getWeaponName()+"额外增加"+ weapon.getHurtPoints()+"点攻击力 q.拾取  任意键.舍弃 ");
        String answer = sc.nextLine();
        if(answer.equals("q")){
            role.setWeapon(weapon);
            role.getBag().add(weapon);
            System.out.print("你已拾取"+ role.getWeapon().getWeaponName());
            System.out.println("  攻击力加"+weapon.getHurtPoints());
        }else{
            System.out.println("你已丢弃"+weapon.getWeaponName());
        }
        System.out.println("继续探索吧    e:查看背包 r:使用药水恢复生命值 t:查看当前角色状态");
        maze[x][y] = door;
    }
    //捡到盔甲
    private static void defense(int x, int y, Role role, int[][] maze, ArrayList<Equipment> Armors,Scanner sc) {
        Random rand = new Random();
        int index = rand.nextInt(3) + 6;
        Armor armor = (Armor)Armors.get(index);
        System.out.println("你捡到了"+armor.getArmorName()+"额外增加"+armor.getDefensePoints()+"点防御值  q.拾取   任意键.舍弃 ");
        String answer = sc.nextLine();
        if(answer.equals("q")){
            role.setArmor(armor);
            role.getBag().add(armor);
            System.out.print("你已拾取" + role.getArmor().armorName);
            System.out.println("  防御值加" + armor.getDefensePoints());
        }else {
            System.out.println("你已丢弃"+armor.getArmorName());
        }
        System.out.println("继续探索吧    e:查看背包 r:使用药水恢复生命值 t:查看当前角色状态");
        maze[x][y] = door;
    }
    //捡到回复药水
    private static void recovery(int x, int y, Role role, int[][] maze, ArrayList<Equipment> Points,Scanner sc) {
        Random r = new Random();
        int index = r.nextInt(3);
        Potion potion = (Potion) Points.get(index);
        System.out.println("你捡到了"+ potion.getPotionName() +"，该药水可回复"+potion.getPotionName()+"点生命值 q.拾取   任意键.舍弃 " );
        String answer = sc.nextLine();
        if(answer.equals("q")){
            role.setPotion(potion);
            role.getBag().add(potion);
            System.out.println("你已拾取" + role.getPotion().getPotionName());
        } else {
            System.out.println("你已丢弃"+potion.getPotionName());
        }
        System.out.println("继续探索吧    e:查看背包  r:使用药水恢复生命值 t:查看当前角色状态");
        maze[x][y] = door;
    }

    //遇到怪物选择战斗或逃跑
    private static void fight(int x, int y, Role role, int[][] maze,Scanner sc) {
        Random r = new Random();
        int random = r.nextInt(3);
        Monster monster1;
        if(random == 0){
             monster1 = new Monster("哥布林",50,2,20);
        }else if(random == 1){
             monster1 = new Monster("史莱姆",30,5,1);
        }else {
             monster1 = new Monster("狼人",100,10,30);
        }
        System.out.println("你遇到 "+ monster1.getMonsterName()+" 生命值:"+ monster1.getHealthPoints() + ": 防御值 :" + monster1.getDefensePoints());
        System.out.println("一点防御值可抵抗两点伤害");
        System.out.println("q: 攻击  r:逃跑 ");
        while (true){
            String answer = sc.nextLine();
            if(answer.equals("q")){
                fighting(x,y,role,monster1,maze);
                break;
            }else if(answer.equals("r")){
                escape(role,monster1);
                break;
            }else {
                System.out.println("你只能选择攻击与逃跑，请重新选择");
            }
        }
    }

    //战斗
    private static void fighting( int x,int y,Role role ,Monster monster1,int[][] maze) {
        while (true){
            //角色攻击
            int roleAttackPoint = (role.getAttackPoints() - monster1.getDefensePoints()*2);//角色能够造成的基础伤害
            if(role.getWeapon()!=null){
                roleAttackPoint = role.getWeapon().getHurtPoints();//有武器加上武器伤害
            }
            if(roleAttackPoint <= 0){
                System.out.println("你的攻击力太低了，无法打破怪物防御，快去拾取武器增加你的攻击力吧");
                escape(role,monster1);
                break;
            }else {
                System.out.println("你对怪物造成"+ roleAttackPoint + "点伤害");
                monster1.setHealthPoints(monster1.getHealthPoints() -  roleAttackPoint);//怪物扣血
            }
            //怪物攻击
            if(role.getArmor() != null){//角色有防御
                int monsterAttackPoint = monster1.getAttackPoints() - role.getArmor().getDefensePoints()*2;//怪物攻击值-角色两倍防御值
                if(monsterAttackPoint <=0){
                    System.out.println("你的防御值很高，怪物无法对你造成伤害,怪物逃跑了");
                    maze[x][y] = door;
                    break;
                }else {
                    System.out.println("怪物对你造成"+monsterAttackPoint+ "点伤害");
                    role.setBlood(role.getBlood() - monsterAttackPoint);
                }
            }else {//角色无防御
                System.out.println("怪物对你造成"+monster1.getAttackPoints()+ "点伤害");
                role.setBlood(role.getBlood() - monster1.getAttackPoints());
            }

            if(role.getBlood() <=0){
                System.out.println("你被击败了");
                break;
            }else if (monster1.getHealthPoints() <= 0){
                System.out.println("你成功击败"+ monster1.getMonsterName());
                maze[x][y] = door;
                break;
            }
        }
    }

    //逃跑
    private static void escape(Role role,Monster monster1){
        Random rand = new Random();
        int runAttacked = rand.nextInt(monster1.getAttackPoints()) + monster1.getAttackPoints() /2;
        role.setBlood(role.getBlood() - runAttacked);//逃跑随机扣除大于怪物伤害一半的生命值
        System.out.println("你逃跑了,但受到"+ runAttacked + "点伤害");
        System.out.println("你当前生命值:" + role.getBlood());
    }

    //移动后
    private static void walk(int x, int y, Role role, int[][] maze,ArrayList<Equipment> equipments) {
        Scanner sc = new Scanner(System.in);
        switch (maze[x][y]) {
            case monster:
                fight(x,y,role,maze,sc);
                break;
            case potion:
                recovery(x,y,role,maze,equipments,sc);
                break;
            case armor:
                defense(x,y,role,maze,equipments,sc);
                break;
            case weapon:
                offense(x,y,role,maze,equipments,sc);
                break;
            default:
                break;
        }
    }
    //上下左右移动
    private static int up(int x, int y, Role role,int[][] maze){
        int temp = x;
        if(x == 0){
            //走到边界
            boundary();
            printMaze(maze,x,y,role);
        }else if(maze[--temp][y] == wall){
            //撞墙
            wall();
            printMaze(maze,x,y,role);
        }else{
            x--;
            printMaze(maze,x,y,role);
        }
        return x;
    }
    private static int down(int x, int y, Role role, int[][] maze) {
        int temp = x;
        if(x == (col - 1)){
            boundary();
            printMaze(maze,x,y,role);
        }else if(maze[++temp][y] == wall){
            wall();
            printMaze(maze,x,y,role);
        }else{
            x++;
            printMaze(maze,x,y,role);
        }
        return x;
    }
    private static int left(int x, int y, Role role, int[][] maze) {
        int temp = y;
        if(y == 0){
            boundary();
            printMaze(maze,x,y,role);
        }else if(maze[x][--temp] == wall){
            wall();
            printMaze(maze,x,y,role);
        }else{
            y--;
            printMaze(maze,x,y,role);
        }
        return y;
    }
    private static int right(int x, int y, Role role, int[][] maze) {
        int temp = y;
        if(y == (row -1) ){
            boundary();
            printMaze(maze,x,y,role);
        }else if(maze[x][++temp] == wall){
            wall();
            printMaze(maze,x,y,role);
        }else{
            y++;
            printMaze(maze,x,y,role);
        }
        return y;
    }

    //查看状态
    private static void lookRoleState(Role role) {
        System.out.println("当前生命值"+role.getBlood());
        if(role.getWeapon() != null){
            System.out.println("当前攻击值"+ (20 +role.getWeapon().getHurtPoints()));
        }else {
            System.out.println("你还未获得任何武器，当前攻击值为"+ 20);
        }
        if(role.getArmor() != null){
            System.out.println("当前防御值"+ role.getArmor().getDefensePoints());
        }else {
            System.out.println("你还未获得任何装备, 当前防御值为"+ 0);
        }
    }
    //使用药水
    private static void usePotion(ArrayList<Equipment> bag ,Role role) {
        if(role.getBlood() == 100){
            System.out.println("你的生命值是满的，无需使用药水");
            return;
        }
        boolean potionExist = false;
        for (int i = 0; i < bag.size(); i++) {
            if (bag.get(i) instanceof Potion){
                int recoveryPoint = ((Potion) bag.get(i)).getRecoveryPoints();
                if(100 - role.getBlood() > recoveryPoint){
                    role.setBlood(role.getBlood()+ recoveryPoint);
                }else {
                    recoveryPoint = 100 - role.getBlood();
                    role.setBlood(100);
                }
                System.out.print("你使用了" + ((Potion) bag.get(i)).getPotionName());
                System.out.println("回复了"+recoveryPoint+"点生命值");
                System.out.println("你当前的生命值为"+ role.getBlood());
                bag.remove(i);
                potionExist = true;
                break;
            }
        }
        if(!potionExist){
            System.out.println("你还未捡到药水 迷宫里 ◈ 是药水，快去拾取吧");
        }
    }
    //查看背包
    private static void lookBag(Role role){
        if(role.getBag().isEmpty()){
            System.out.println("背包是空的，快去拾取装备吧");
            return;
        }
        for (int i = 0; i < role.getBag().size(); i++) {
            if(role.getBag().get(i) instanceof Weapon){
                System.out.print(((Weapon) role.getBag().get(i)).getWeaponName() + "  ");
            }else if(role.getBag().get(i) instanceof Armor){
                System.out.print(((Armor) role.getBag().get(i)).getArmorName() + "  ");
            }else if (role.getBag().get(i) instanceof  Potion){
                System.out.print(((Potion) role.getBag().get(i)).getPotionName() + "  ");
            }
        }
    }
    //撞墙提示
    private static void wall(){
        System.out.println("这个方向是墙壁，请重新移动");
    }
    //边界提示
    private static void boundary(){
        System.out.println("抱歉，你不能再向这个方向移动,请重新输入指令");
    }
    //打印迷宫
    private static void printMaze(int[][] maze, int x, int y, Role role){
        for(int i = 0 ;  i < maze.length ; i++){
            for(int j = 0 ;j < maze[i].length ;j++){
                if( x== i && y == j){
                    System.out.print(role.getRole() + " ");
                }else if(maze[i][j] == potion){
                    System.out.print( "◈"  + " ");
                }else if (maze[i][j] == wall) {
                    System.out.print("▣" + " ");
                } else {
                    System.out.print("▢" + " ");
                }
            }
            System.out.println();
        }
    }
    //初始化迷宫
    private static int[][] generateMaze(int row , int col){
        int[][] arr = new int[row][col];
        Random r = new Random();
        //30%概率生成陆地 20%的概率生成障碍 20%概率生成怪物 10%概率生成药水 10%概率生成盔甲 10%概率生成装备
        int [] may = {door,door,door,wall,wall,monster,monster,potion,armor,weapon};
        for (int i = 0; i < arr.length; i++) {
            for (int j = 0; j < arr[i].length; j++) {
                int random = r.nextInt(10);
                arr[i][j] = may[random];
                if( (i == 0 && j == 0 )|| (i ==  arr.length - 1 && j == arr[i].length - 1)){
                    arr[i][j] = door;
                }
            }
        }
        return arr;
    }
    //打印菜单，玩法说明
    private static void printMenu(){
        System.out.println("-----------欢迎玩耍走迷宫游戏--------------------");
        System.out.println("-----------玩法：w 上       e:查看背包 ----------");
        System.out.println("-----------左 a  s  d 右   r:使用药水恢复生命值---");
        System.out.println("-----------     下         t:查看当前角色状态-----");
        System.out.println("-----------拾取装备后自动使用该装备----------------");
    }
    //创建装备
    private static ArrayList<Equipment> createEquipment() {
        ArrayList<Equipment> equipments = new ArrayList<>();
        Potion potion0 = new Potion("小瓶药水",10);
        Potion potion1 = new Potion("中瓶药水",20);
        Potion potion2 = new Potion("大瓶药水",30);

        Weapon weapon3 = new Weapon("方天画戟",30);
        Weapon weapon4 = new Weapon("青龙偃月刀",35);
        Weapon weapon5 = new Weapon("丈八蛇矛",25);

        Armor armor6 = new Armor("藤甲",10);
        Armor armor7 = new Armor("白银狮子",15);
        Armor armor8 = new Armor("仁王盾",20);

        equipments.add(potion0);
        equipments.add(potion1);
        equipments.add(potion2);

        equipments.add(weapon3);
        equipments.add(weapon4);
        equipments.add(weapon5);

        equipments.add(armor6);
        equipments.add(armor7);
        equipments.add(armor8);
        return equipments;
    }

}
